home *** CD-ROM | disk | FTP | other *** search
/ Language/OS - Multiplatform Resource Library / LANGUAGE OS.iso / p4 / p4-1_2c.lha / p4-1.2c / messages / grid_master.c < prev    next >
C/C++ Source or Header  |  1993-05-24  |  6KB  |  279 lines

  1. #include "p4.h"
  2.  
  3. #ifndef TRUE
  4. #define BOOL            int
  5. #define TRUE            1
  6. #define FALSE           0
  7. #endif
  8.  
  9. /*  the following numbers define a grid of 4 processes, plus one master */
  10. #define ROWS        100
  11. #define COLUMNS        100
  12.  
  13. #define ROWS_PER_SUB     50
  14. #define COLUMNS_PER_SUB 50
  15.  
  16.  
  17.  
  18. #define PROCS_PER_COL    (ROWS / ROWS_PER_SUB)
  19. #define PROCS_PER_ROW    (COLUMNS / COLUMNS_PER_SUB)
  20. #define N_PROCS        (PROCS_PER_ROW * PROCS_PER_COL)
  21.  
  22. /* message types */
  23. #define CNTL            0
  24. #define C_BOUNDARY    1
  25. #define R_BOUNDARY    2
  26. #define ANSWER          3
  27.  
  28. #define MASTER        0    /*master proc id */
  29.  
  30. struct cntl_rec {
  31.       int row;
  32.     int col;
  33.         int upper_neighbor;
  34.     int right_neighbor;
  35.     int lower_neighbor;
  36.     int left_neighbor;
  37.     int iterations;
  38.     double bounded_subgrid[ROWS_PER_SUB+2][COLUMNS_PER_SUB+2];
  39.     };
  40.  
  41. struct c_boundary {
  42.     double col[ROWS_PER_SUB];
  43.     };        
  44.  
  45. struct r_boundary {
  46.            double row[COLUMNS_PER_SUB];
  47.     };
  48.  
  49. struct answer_rec {
  50.     double subgrid[ROWS_PER_SUB][COLUMNS_PER_SUB];
  51.         };
  52.  
  53. double avggrid();
  54. double avgbnd();
  55.  
  56. /* some compilers require this to be outside main (too many locals) */
  57. double  grid[ROWS+2][COLUMNS+2];
  58.  
  59.  
  60. main(argc,argv)
  61. int argc;
  62. char *argv[];
  63. {
  64.  
  65.     struct cntl_rec rec1;
  66.     struct answer_rec *rec2;
  67.  
  68.     int        process_id[N_PROCS], proc_id;
  69.     int     proc, i, j, f_row, f_col, ln, msg_type;
  70.     int timestart, timeend;
  71.     double avg;
  72.  
  73.     p4_initenv(&argc,argv);
  74.     p4_create_procgroup();
  75.     if (p4_get_my_id() != 0)
  76.     {
  77.     slave();
  78.     exit(0);
  79.     }
  80.  
  81.     /*  old way - RL
  82.     gridinit(grid,ROWS+2,COLUMNS+2);
  83.     */
  84.     gridinit(grid,ROWS,COLUMNS);
  85.  
  86.     printf("Enter the number of iterations: ");
  87.     scanf("%d",&(rec1.iterations));        
  88.  
  89.     timestart = p4_clock();
  90.  
  91.     for (proc=0; proc < N_PROCS; proc++)
  92.     process_id[proc] = proc+1;
  93.  
  94.     for (proc=0; proc < N_PROCS; proc++)
  95.     {
  96.     rec1.row = first_row(proc);
  97.     rec1.col = first_column(proc);
  98.     rec1.left_neighbor = 0;
  99.     rec1.right_neighbor = 0;
  100.     rec1.upper_neighbor = 0;
  101.     rec1.lower_neighbor = 0;
  102.     if (!upper_bound(rec1.row)) {
  103.         i = rec1.row - ROWS_PER_SUB;
  104.         j = which_proc(i,rec1.col);
  105.         rec1.upper_neighbor = process_id[j];
  106.     }
  107.     if (!lower_bound(rec1.row)) {
  108.         i = rec1.row + ROWS_PER_SUB;
  109.         j = which_proc(i,rec1.col);
  110.         rec1.lower_neighbor = process_id[j];
  111.     }
  112.     if (!right_bound(rec1.col)) {
  113.         i = rec1.col + COLUMNS_PER_SUB;
  114.         j = which_proc(rec1.row,i);
  115.         rec1.right_neighbor = process_id[j];
  116.     }
  117.     if (!left_bound(rec1.col)) {
  118.         i = rec1.col - COLUMNS_PER_SUB;
  119.         j = which_proc(rec1.row,i);
  120.         rec1.left_neighbor = process_id[j];
  121.     }
  122.  
  123.     for (i=(rec1.row - 1); i <= (rec1.row + ROWS_PER_SUB); i++) 
  124.     {
  125.  
  126.         for (j=(rec1.col - 1); j <= (rec1.col + COLUMNS_PER_SUB); j++)
  127.         {
  128.         rec1.bounded_subgrid[(i-(rec1.row-1))][(j-(rec1.col-1))] =
  129.             grid[i][j];
  130.         }
  131.     }
  132.     ln = sizeof(struct cntl_rec);
  133.     p4_sendr(CNTL,process_id[proc],&rec1,ln);
  134.     }
  135.  
  136.     for (proc=0; proc < N_PROCS; proc++)
  137.     {
  138.     p4_dprintfl(5,"master receiving answer\n");
  139.     
  140.     msg_type = ANSWER;
  141.     proc_id = -1; 
  142.     rec2 = NULL;
  143.     p4_recv(&msg_type,&proc_id,&rec2,&ln);
  144.     p4_dprintfl(5,"master received answer from slave %d\n",proc_id);
  145.     f_row = first_row(proc_id - 1);
  146.     f_col = first_column(proc_id - 1);
  147.     for (i=0; i < ROWS_PER_SUB; i++) 
  148.         for (j=0; j < COLUMNS_PER_SUB; j++)
  149.         grid[f_row + i][f_col + j] = rec2->subgrid[i][j];
  150.     }
  151.     timeend = p4_clock();
  152.     printf("total time %.3f seconds\n",(timeend - timestart)/1000.0);
  153.     p4_wait_for_end();
  154.  
  155.     /* printgrid(grid,ROWS,COLUMNS); */
  156.     avg = avggrid(grid,ROWS,COLUMNS);
  157.     printf("average value of grid = %f\n",avg);
  158. }
  159.  
  160. first_row(proc)
  161. int proc;
  162. {
  163.     return(((proc / PROCS_PER_ROW) * ROWS_PER_SUB) + 1);
  164. }
  165.  
  166. first_column(proc)
  167. int proc;
  168. {
  169.     return(((proc % PROCS_PER_ROW) * COLUMNS_PER_SUB) + 1);
  170. }
  171.  
  172. which_proc(row,column)
  173. int row,column;
  174. {
  175.     return((((row - 1) / ROWS_PER_SUB) * PROCS_PER_ROW) + 
  176.        ((column - 1) / COLUMNS_PER_SUB));
  177. }
  178.  
  179. /* old way - RL
  180. gridinit(m,x,y)
  181. double m[ROWS+2][COLUMNS+2];
  182. int x,y;
  183. {
  184.     int i, j;
  185.  
  186.     for (i=0; i <= x-1; i++)
  187.         for (j=0; j <= y-1; j++)
  188.             m[i][j] = 0;
  189.  
  190.     for (j=0; j < y; j++)
  191.     {
  192.         m[0][j] = phi(1,j+1);
  193.         m[x-1][j]= phi(x+1,j+1);
  194.     }
  195.     for (i=0; i < x; i++)
  196.     {
  197.         m[i][0] = phi(i+1,1);
  198.         m[i][y-1] = phi(i+1,y+1);
  199.     }
  200. }
  201. */
  202.  
  203.  
  204. gridinit(m,r,c)
  205. double m[ROWS+2][COLUMNS+2];
  206. int r, c;
  207. {
  208.     int i, j;
  209.     double bndavg;
  210.     
  211.     for (j=0; j < (c + 2); j++)
  212.     {
  213.         m[0][j] = phi(1,j+1);
  214.         m[r+1][j]= phi(r+2,j+1);
  215.     }
  216.     for (i=1; i < (r + 2); i++)
  217.     {
  218.         m[i][0] = phi(i+1,1);
  219.         m[i][c+1] = phi(i+1,c+2);
  220.     }
  221.     bndavg = avgbnd(m,r,c);
  222.     printf("boundary average = %f\n",bndavg);
  223.  
  224.     /* initialize the interior of the grids to the average over the boundary*/
  225.     for (i=1; i <= r; i++)
  226.         for (j=1; j <= c; j++)
  227.             /* m[i][j] = bndavg; this optimization hinders debugging */
  228.         m[i][j] = 0;
  229. }
  230.  
  231. double avggrid(m,r,c)
  232. double m[ROWS+2][COLUMNS+2];
  233. int r,c;
  234. {
  235.     int i,j;
  236.     double avg = 0;
  237.  
  238.     for (i = 0; i < (r+2); i++)
  239.     for (j = 0; j < (c+2); j++)
  240.         avg += m[i][j];
  241.     return(avg/((r+2)*(c+2)));
  242. }
  243.  
  244. double avgbnd(m,r,c)
  245. double m[ROWS+2][COLUMNS+2];
  246. int r,c;
  247. {
  248.     int i,j;
  249.     double avg = 0;
  250.  
  251.     for (i = 0; i < (r+2); i++)
  252.         avg += m[i][0];
  253.     for (i = 0; i < (r+2); i++)
  254.         avg += m[i][c+1];
  255.     for (i = 1; i < (c+1); i++)
  256.         avg += m[0][i];
  257.     for (i = 1; i < (c+1); i++)
  258.         avg += m[r+1][i];
  259.     return(avg/(2*(c+2) + 2*(r+2) - 4)); /* average over boundary */
  260. }
  261.  
  262. phi(x,y)
  263. int x,y;
  264. {
  265.     return(x*x-y*y+x*y);
  266. }
  267.  
  268. printgrid(grid,r,c)
  269. double grid[ROWS+2][COLUMNS+2];
  270. int r,c;
  271. {
  272.     int i,j;
  273.  
  274.     for (i = 0; i < (r+2); i++)
  275.     for (j = 0; j < (c+2); j++)
  276.         printf("grid[%3d][%3d] = %10.5f\n",i,j,grid[i][j]);
  277. }
  278.  
  279.